/**
 * 
 */
package com.game.jumpdino;

import com.game.jumpdino.logic.GameState;
import com.game.jumpdino.logic.Playground;

import android.content.Context;
import android.graphics.Canvas;
import android.hardware.Sensor;
import android.hardware.SensorManager;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.SurfaceHolder;

/**
 * @author HugoGu
 * 
 */
public class GameThread extends Thread {
	protected SwitchViewHandler viewHandler;
	private SurfaceHolder mSurface;
	private Playground mPlayground;
	private boolean mRun;
	
	public GameThread(SurfaceHolder surfaceHolder, Context context) {
		mSurface = surfaceHolder;
		mPlayground = new Playground(context);
		mRun = true;
	}

	public Playground getPlayground() {
		return mPlayground;
	}
	
	public void setHandler(SwitchViewHandler handler){
		viewHandler = handler;
	}
	
	public void doSensorChanged(Sensor sensor, float[] values){
		synchronized (mSurface) {
			int accel = (int)(values[SensorManager.DATA_X]);
			if (accel > 0){
				mPlayground.movingDirection = 1 * mPlayground.getReverseOperation();
			} else if (accel < 0) {
				mPlayground.movingDirection = -1 * mPlayground.getReverseOperation();
			} else {
				// Do nothing, at most time, accel is 0;
				// User won't like to move the phone all the time.
			}
		}
	}
	
	// @aiyue 0928
	public void doSensor(float value) {
			int vx = 0;
			int sign = value>0 ? 1 : -1;
			if (Math.abs(value) > 1 && Math.abs(value) < 2) {
				vx = sign*3;
			}
			else if (Math.abs(value) >= 2) {
				vx = sign*6;
			}
			if (mPlayground != null) {
				if (mPlayground.avatar != null) {
					mPlayground.avatar.setVx(-vx * mPlayground.getReverseOperation());
					mPlayground.avatar.updateVelocity(-vx * mPlayground.getReverseOperation(), 0);
				}
			}
	}

	public boolean doKeyDown(int keyCode, KeyEvent msg) {
		synchronized (mSurface) {
			if (keyCode == KeyEvent.KEYCODE_DPAD_LEFT) {
				mPlayground.isLeftPressed = true;
				mPlayground.movingDirection = -1 * mPlayground.getReverseOperation();
				return true;
			} else if (keyCode == KeyEvent.KEYCODE_DPAD_RIGHT) {
				mPlayground.isRightPressed = true;
				mPlayground.movingDirection = 1 * mPlayground.getReverseOperation();
				return true;
			} else {
				return false;
			}
		}
	}

	public boolean doKeyUp(int keyCode, KeyEvent msg) {
		synchronized (mSurface) {
			if (keyCode == KeyEvent.KEYCODE_DPAD_LEFT) {				
				if (mPlayground.isRightPressed){
					mPlayground.movingDirection = 1 * mPlayground.getReverseOperation();
				} else {
					mPlayground.movingDirection = 0;
				}
				mPlayground.isLeftPressed = false;
				return true;
			} else if (keyCode == KeyEvent.KEYCODE_DPAD_RIGHT) {
				if (mPlayground.isLeftPressed){
					mPlayground.movingDirection = -1 * mPlayground.getReverseOperation();
				} else {
					mPlayground.movingDirection = 0;
				}
				mPlayground.isRightPressed = false;
				return true;
			} else {
				return false;
			}
		}
	}
	
    /**
     * Pauses the physics update & animation.
     */
    public void pause() {
        synchronized (mSurface) {
            if (mPlayground.getState() == GameState.Started){
            	mPlayground.setState(GameState.Paused);
            }
        }
    }
    
    public void restartGame(){
        synchronized (mSurface) {
            if (mPlayground.getState() == GameState.Started){
            	mPlayground.setState(GameState.Ready);
            }
        }
    }
    
    public void stopGame(){
        synchronized (mSurface) {
            if (mPlayground.getState() == GameState.Started){
            	mPlayground.setState(GameState.Stoped);
            }
        }
    }
    
    public void resumeGame(){
        synchronized (mSurface) {
            if (mPlayground.getState() == GameState.Paused){
            	mPlayground.setState(GameState.Started);
            }
        }
    }
    
    /**
     * Dump game state to the provided Bundle. Typically called when the
     * Activity is being suspended.
     * 
     * @return Bundle with this view's state
     */
    @SuppressWarnings("static-access")
    public Bundle saveState(Bundle map) {
        synchronized (mSurface) {
            if (map != null) { 
            	
            }
        }
        return map;
    }
    
    @SuppressWarnings("static-access")
    public synchronized void restoreState(Bundle savedState) {
        synchronized (mSurface) {
        	if (savedState != null){
        	
        	}
        }
    }

    /*
	while (!Thread.currentThread().isInterrupted()) {
		Canvas c = null;
		try {
			if (mPlayground.getState() == GameState.Ready) {
				mPlayground.Reset();
			}
			if (mPlayground.getState() == GameState.NewLife) {
				if (viewHandler != null) {
					viewHandler.setLife(mPlayground.getLifeCount());
				}
				mPlayground.newMatch();
				// mPlayground.score = 0;
			}
			if (mPlayground.getState() == GameState.Started) {
				mPlayground.doMove();

			}
			if (mPlayground.getState() == GameState.Stoped) {
				// Thread stop and View destroy and show Over view.
				// mRun = false;
				Thread.currentThread().interrupt();
				mPlayground.score = 0;
				if (viewHandler != null) {
					if (!viewHandler.isInFinishView()) {
						viewHandler.switchToFinish();
					}
				}
			}
			if (mPlayground.getState() == GameState.Over) {
				// todo: need to add high score here
				// mRun = false;
				Thread.currentThread().interrupt();
			}
			if (mPlayground.getState() == GameState.Started) {
				c = mSurface.lockCanvas(null);
				synchronized (mSurface) {
					if (viewHandler != null) {
						viewHandler.showScore(mPlayground.score);
					}
					mPlayground.drawOn(c);
				}
			}
*/
    
   
	@SuppressWarnings("static-access")
	@Override
	public void run() { 
		while (mRun) {
			Canvas c = null;
			try {
				
				
					if (mPlayground.getState() == GameState.Ready){
						mPlayground.Reset();
					}
					if (mPlayground.getState() == GameState.NewLife){
						if (viewHandler != null){
							viewHandler.setLife(mPlayground.getLifeCount());
						}
						mPlayground.newMatch();
					}
					if (mPlayground.getState() == GameState.Started ) {
						mPlayground.doMove();
					}
					if (mPlayground.getState() == GameState.Stoped) {
						// Thread stop and View destroy and show Over view.
						mRun = false;
						mPlayground.score = 0;
						if (viewHandler != null){
							if (!viewHandler.isInFinishView()){
								viewHandler.switchToFinish();
							}
						}
					}
					if (mPlayground.getState() == GameState.Over){
						// todo: need to add high score here
						mRun = false;
					}
					if (mPlayground.getState() == GameState.Started){
						c = mSurface.lockCanvas(null);
						synchronized (mSurface) {
							if (viewHandler != null){
								viewHandler.showScore(mPlayground.score);
							}
							mPlayground.drawOn(c);
						}
					}				
			
				// tony
				 if (mPlayground.getState() == GameState.Paused){
					sleep(1);
				 }
			} catch (InterruptedException e) {
				// e.printStackTrace();
			}finally {
				// do this in a finally so that if an exception is thrown
				// during the above, we don't leave the Surface in an
				// inconsistent state
				if (c != null) {
					mSurface.unlockCanvasAndPost(c);
				}
			}
		}
	}
		
    
	
}
